package com.ruoyi.file.utils;

import com.ruoyi.common.core.exception.file.FileException;
import com.ruoyi.common.core.exception.file.FileNameLengthLimitExceededException;
import com.ruoyi.common.core.exception.file.FileSizeLimitExceededException;
import com.ruoyi.common.core.exception.file.InvalidExtensionException;
import com.ruoyi.common.core.utils.DateUtils;
import com.ruoyi.common.core.utils.StringUtils;
import com.ruoyi.common.core.utils.file.FileTypeUtils;
import com.ruoyi.common.core.utils.file.MimeTypeUtils;
import com.ruoyi.common.core.utils.uuid.Seq;
import org.apache.commons.io.FileUtils;
import org.apache.commons.io.FilenameUtils;
import org.jaudiotagger.audio.AudioFile;
import org.jaudiotagger.audio.wav.WavFileReader;
import org.springframework.web.multipart.MultipartFile;
import org.vosk.Model;
import org.vosk.Recognizer;

import javax.sound.sampled.AudioSystem;
import javax.swing.*;
import java.io.*;
import java.nio.file.Paths;
import java.util.Objects;

/**
 * 语音识别工具类
 * 
 * @author ruoyi
 */
public class SpeechVoskUtils
{
    private SpeechVoskUtils() {}
    private static class SingletonInner {
        private static SpeechVoskUtils singletonStaticInner = new SpeechVoskUtils();
    }
    private static  Model model;
    public static SpeechVoskUtils getInstance() {
        String modelPath = System.getProperty("user.dir") + "/src/main/resources/vosk-model-small-cn-0.22"; // 初始化模型

        try {
            model = new Model(modelPath);//该段是模型地址

        } catch (Exception e) {
            e.printStackTrace();
        }
        return SingletonInner.singletonStaticInner;
    }

    /**
     * 根据文件路径上传
     * @param multipartFile 上传的文件
     * @return 文件名称
     * @throws IOException
     */
    public static String speech(MultipartFile multipartFile) throws Exception
    {
        String originalFilename = multipartFile.getOriginalFilename(); // 获取原始文件名
        int lastDotIndex = originalFilename.lastIndexOf("."); // 查找最后一个点号的索引位置
        if (lastDotIndex != -1) {
            String fileExtension = originalFilename.substring(lastDotIndex + 1); // 提取文件后缀
            File tempFile = File.createTempFile("temp_", fileExtension);
            FileUtils.copyInputStreamToFile(multipartFile.getInputStream(), tempFile);
            return speech(tempFile);
        }
        return null;
    }
    /**
     * 根据文件路径上传
     * @param file 上传的文件
     * @return 文件名称
     * @throws IOException
     */
    public static String speech(File file) throws Exception
    {

        InputStream ais = AudioSystem.getAudioInputStream(new BufferedInputStream(new FileInputStream(file))); //该段是要转的语言文件，仅支持wav
        Recognizer recognizer = new Recognizer(model, getSampleRate(file));  //该段中12000是语言频率(Hz)，需要大于8000，可以自行调整

        int bytes;
        byte[] b = new byte[4096];
        while ((bytes = ais.read(b)) >= 0) {
            recognizer.acceptWaveForm(b, bytes);
        }
        return recognizer.getFinalResult();
    }
    /**
     * 获取音频文件的采样率
     */
    private static Float getSampleRate(File file) throws Exception {
        WavFileReader fileReader = new WavFileReader();
        AudioFile audioFile = fileReader.read(file);
        String sampleRate = audioFile.getAudioHeader().getSampleRate();
        return Float.parseFloat(sampleRate);
    }
}